#ifndef _CALLDLL_H_
#define _CALLDLL_H_

#ifdef  __cplusplus



		#ifndef offsetof
		#define offsetof(s,m) ((size_t)&reinterpret_cast<char const volatile&>((((s*)0)->m)))
		#endif // !offsetof

		class CPP_NO_VTABLE IImpModuleBase
		{
		public:
			struct STFunDesc
			{
				char *pFunName;
				size_t uOffFun;
			};
		public:

			TCHAR m_szModuleName[MAX_PATH];
			HMODULE m_hMod;	
			virtual void InitIAT()
			{
				STFunDesc *pFunDesc=GetFunDefs();
				while(pFunDesc->pFunName)
				{	
					pFunDesc++;
				}
			}
		public:
			IImpModuleBase(const TCHAR *pModuleName):m_hMod(NULL)
			{

			}
			virtual ~IImpModuleBase()
			{
				UnLoad();
			}	
			virtual int Load()
			{
				iosprintf("IImpModuleBase->Load")
				STFunDesc *pFunDesc=GetFunDefs();
				m_hMod = loadlib(m_szModuleName, RTLD_LAZY);
				if (!m_hMod)
					return -1;

				while(string_stricmp(pFunDesc->pFunName,"null") != 0)
				{
					void *p = libfunc(m_hMod,pFunDesc->pFunName);

					setfuncaddress(pFunDesc->uOffFun,p);
					if (!p)
					{
						if(Exception(m_hMod, pFunDesc->pFunName))
							return -1;
					}
					pFunDesc++;
				}
					
				return 1;
			}
			virtual int UnLoad()
			{
			
				if(m_hMod)
				{
					closelib(m_hMod);
				}
				m_hMod = NULL;
			
				return 0;
			}
			virtual bool IsLoaded()
			{
				return NULL != m_hMod;
			}
			virtual bool Exception(HMODULE hModule, const char* lpProcName)
			{
				iosprintf("IImpModuleBase->Exception")
				return true;
			}
			virtual STFunDesc *GetFunDefs() 			= 0;
			virtual bool setfuncaddress(int i,void *p) 	= 0;
		};


#endif //  __cplusplus

#endif 
